package com.qipay.admin.home.controller;

import com.qipay.admin.home.vo.UploadParam;
import com.qipay.admin.login.AuthPassport;
import com.qipay.admin.msg.vo.MessageJSONDTO;
import com.qipay.admin.withdraw.service.WithdrawLogicService;
import com.qipay.baas.model.*;
import com.qipay.channelType.ChannelTypeService;
import com.qipay.cp.CpService;
import com.qipay.cpchannel.service.CpChannelService;
import com.qipay.doc.service.ActionDocService;
import com.qipay.msg.MessageService;
import com.qipay.resource.config.ResourceStatusEnum;
import com.qipay.resource.entity.Resource;
import com.qipay.resource.service.ResourceService;
import com.qipay.security.UserDetailsServiceImpl;
import com.qipay.sp.*;
import com.qipay.user.entity.UserLevel;
import com.qipay.utils.Result;
import org.apache.tomcat.util.http.fileupload.IOUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.annotation.AuthenticationPrincipal;
import org.springframework.util.Assert;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.InputStream;
import java.io.UnsupportedEncodingException;
import java.math.BigDecimal;
import java.net.URLDecoder;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;


/**
 * Created by dong on 2016/6/13.
 */
@RestController
public class AjaxController {

    @Autowired
    CpService cpService;
    @Autowired
    CpChannelService cpChannelService;
    @Autowired
    SpChannelRuleService spChannelRuleService;

    @Autowired
    ActionDocService actionDocService;
    @Autowired
    SpService spService;
    @Autowired
    SpChannelService spChannelService;
    @Autowired
    SpApiConfigService spApiConfigService;
    @Autowired
    SpConfigService spConfigService;
    Logger logger = LoggerFactory.getLogger(AjaxController.class);

    @Autowired
    ResourceService resourceService;

    @Autowired
    MessageService messageService;

    @Autowired
    ChannelTypeService channelTypeService;

    @Autowired
    WithdrawLogicService withdrawLogicService;



    @RequestMapping(value = "/ajax/msg", method = RequestMethod.GET, produces = "application/json")
    public Result<List<MessageJSONDTO>> ajaxGetUnReadMsg(@AuthenticationPrincipal UserDetailsServiceImpl.LoginUserDetails loginUser) {
        Result<List<MessageJSONDTO>> result = new Result<>();
        result.setCode(0);
        if (loginUser.getLevel() == UserLevel.ADMIN) {
            return result;
        }
        Integer uid = Integer.valueOf(loginUser.getUsername());
        if (uid != null && uid.intValue() > 0) {
            List<Message> lst = messageService.selectUnReadByUid(uid);
            if (lst != null && lst.size() > 0) {
                List<MessageJSONDTO> lstDtos = new ArrayList<>(lst.size());
                for (Message msg : lst) {
                    MessageJSONDTO jsondto = new MessageJSONDTO();
                    BeanUtils.copyProperties(msg, jsondto);
                    lstDtos.add(jsondto);
                }
                result.setCode(200);
                result.setData(lstDtos);
            }
        }
        return result;
    }


    @AuthPassport(key = "admin")
    @RequestMapping(value = "/ajax", method = RequestMethod.GET, produces = "application/json")
    public int ajaxDo(@RequestParam(value = "n", required = false, defaultValue = "") String methodtype,
                      @RequestParam(value = "id", required = false, defaultValue = "0") int id,
                      @RequestParam(value = "id2", required = false, defaultValue = "0") int id2,
                      @RequestParam(value = "cpFeeRecharge", required = false, defaultValue = "0") BigDecimal cpFeeRecharge,
                      @RequestParam(value = "agentFeeRecharge", required = false, defaultValue = "0") BigDecimal agentFeeRecharge,
                      @RequestParam(value = "rateAdvance", required = false, defaultValue = "0") BigDecimal rateAdvance,
                      @RequestParam(value = "s", required = false, defaultValue = "") String info) throws UnsupportedEncodingException {
        if (methodtype != null && methodtype.length() > 0 && id > 0) {
            switch (methodtype) {
                //根据id修改cpFeeRecharge
                case "updatecpFeeRecharge":
                    updatecpFeeRecharge(id,cpFeeRecharge);
                    return 1;
                //根据id修改agentFeeRecharge
                case "updateagentFeeRecharge":
                    updatecAgentFeeRecharge(id,agentFeeRecharge);
                    return 1;
                //根据id修改rateAdvance
                case "updaterateAdvance":
                    updateRateAdvance(id,rateAdvance);
                    return 1;
                case "setcpaccountstate":
                    setCpAccountState(id, id2, info);
                    return 1;
                case "setcpchannelstate":
                    setCpChannelState(id, id2);
                    return 1;
                case "setspchannelstate":
                    setSpChannelState(id, id2);
                    return 1;
                case "setsplstate":
                    setSpState(id, id2);
                    return 1;
                case "setspdeleteflag":
                    setSpdeleteFlag(id);
                    return 1;
                case "deldocbyid":
                    delDocById(id);
                    return 1;
                case "deldocdetailbyid":
                    delDocDetailById(id);
                    return 1;
                case "delapiconfigbyid":
                    delApiConfigById(id);
                    return 1;
                case "delconfigbyid":
                    delConfigById(id);
                    return 1;
                case "delspbyid":
                    delSpById(id);
                    return 1;
                case "deletechanneltype":
                    deletechanneltype(id);
                    return 1;
                case "delcpbyid":
                    delCpById(id);
                    return 1;
                case "delcpchbyid":
                    delCpChById(id);
                    return 1;
                case "delspchbyid":
                    delSpChById(id);
                    return 1;
                case "delchannelType":
                    delChannelType(id);
                    return 1;
                case "findwidthdraw":
                    int num = findWidthDraw();
                    return num;
                case "lnkOpenOrClose":
                    lnkOpenOrClose(id,id2);
                    return 1;

                default:
                    return 0;
            }

        }
        return -1;
    }



    /**
     * 提现，查询区名
     * @return
     */
    @AuthPassport(key = "admin")
    @RequestMapping(value = "/ajaxBanks", method = RequestMethod.GET, produces = "application/json")
    public Result findArea(@RequestParam(value = "province", required = false, defaultValue = "") String province,
                           @RequestParam(value = "city", required = false, defaultValue = "") String city,
                           @RequestParam(value = "bank", required = false, defaultValue = "") String bank
                           ) {
        Result result = new Result<>();
        List<Banks> banks1=withdrawLogicService.getBank(province,city,bank);
        if(banks1!=null && banks1.size()>0){
            result.setData(banks1);
            result.setCode(200);
        }else {
            result.setCode(-1);
            result.setMsg("没有查到信息");
        }
            // {"code":"1101","name":"市辖区","parent_code":"11"}
        return result;
    }


    //根据id修改cpFeeRecharge
    private void updatecpFeeRecharge(int id,BigDecimal cpFeeRecharge) {
        channelTypeService.updateCpFeeRechargeByid(Long.valueOf(id),cpFeeRecharge);
        updateCp(id,1,cpFeeRecharge);
    }

    //根据id修改agentFeeRecharge
    private void updatecAgentFeeRecharge(int id,BigDecimal agentFeeRecharge) {
        channelTypeService.updateAgentFeeRechargeByid(Long.valueOf(id),agentFeeRecharge);
        updateCp(id,2,agentFeeRecharge);
    }

    //根据id修改rateAdvance
    private void updateRateAdvance(int id,BigDecimal rateAdvance) {
        channelTypeService.updateRateAdvanceByid(Long.valueOf(id),rateAdvance);
        updateCp(id,3,rateAdvance);
    }

    private void updateCp(Integer channelTypeId,int type,BigDecimal big){
        List<Cp>cps = cpService.findAll();
        for (Cp c:cps){
            CpChannel cpChannel = cpChannelService.getByCpIdAndChannelType(c.getId(),channelTypeId.byteValue());
            if (cpChannel!=null){
                if(c.getType()==type){
                    cpChannel.setFeeRecharge(big);
                }
                if(type==3){
                    cpChannel.setRateAdvince(big);
                }
                cpChannelService.update(cpChannel);
            }
        }

    }


    private int lnkOpenOrClose(Integer id,Integer state) {
        ChannelType channelType = channelTypeService.findById(id);
        channelTypeService.save(channelType.getId(),state.byteValue());
        List<Cp>cps = cpService.findAll();
        for (Cp c:cps){
            CpChannel cpChannel = cpChannelService.getByCpIdAndChannelType(c.getId(),id.byteValue());
            if (cpChannel!=null&&cpChannel.getState()!=state.byteValue()){
                cpChannelService.updateState(cpChannel.getId(), state.byteValue());
            }
        }
        return 0;
    }

    /**
     * 商户的通道禁用和启用
     * @param id
     * @param id2
     */
    private void setCpChannelState(int id, int id2) {
        byte state = id2 == 200 ? (byte) 0 : 1;
        cpChannelService.updateState(id, state);
    }
    private int openChannelType(int id) {
        int num = ((Long)withdrawLogicService.countApply()).intValue();

        return num;
    }
    private int findWidthDraw() {
        int num = ((Long)withdrawLogicService.countApply()).intValue();

       return num;
    }
    private void delChannelType(int id) {
        if (id > 0) {
            channelTypeService.delete(id);
        }
    }
    private void delSpChById(int id) {
        if (id > 0) {
            spChannelService.delete(id);
        }
    }
    private void delCpChById(int id) {
        if (id > 0) {
            cpChannelService.delete(id);
        }
    }
    private void delCpById(int id) {
        if (id > 0) {
            cpService.delete(id);
        }
    }

    private void delSpById(int id) {
        if (id > 0) {
            spService.delete(id);
        }
    }

    private void deletechanneltype(long id) {
        if (id > 0) {
            spChannelRuleService.delete(id);
        }
    }

    private void setSpState(int id, int id2) {
        byte state = id2 == 200 ? (byte) 0 : 1;
        spService.updateState(id, state);
    }
    //标注为删除标记
    private void setSpdeleteFlag(int id) {
            spService.updateDeleteFlag(id);

    }


    private void delDocDetailById(int id) {
        actionDocService.deleteActionDocDetail(id);
    }

    private void delConfigById(int id) {
        spConfigService.delete(id);
    }

    private void delApiConfigById(int id) {
        spApiConfigService.delete(id);
    }

    private void setSpChannelState(int id, int id2) {
        byte state = id2 == 200 ? (byte) 0 : 1;
        spChannelService.updateState(id, state);
    }

    private void delDocById(int id) {
        actionDocService.deleteActionDoc(id);
    }

    private void setCpAccountState(int id, int id2, String info) throws UnsupportedEncodingException {
        byte state = id2 == 200 ? (byte) 2 : 0;
        cpService.updateAccountState(id, state);
        info = id2 == 200 ? String.format("账号为%s的商户已经审核通过。", id) : URLDecoder.decode(info, "utf8");

        Cp cp = cpService.getOneById(id);
        int agentId = id;
        if (cp != null && cp.getType() != null && cp.getType() == 1) {
            Message message = new Message();
            message.setStatus((byte) 0);
            message.setContent(info);
            message.setCreateTime(new Date());
            message.setSendBy(1);
            message.setSendName("系统");
            message.setType((byte) 0);

            if (cp.getAgentId() != null && cp.getAgentId() > 0) {
                agentId = cp.getAgentId().intValue();
                message.setReceiveBy(agentId);
                message.setReceiveName(String.valueOf(agentId));
                messageService.insert(message);
            }
            message.setReceiveBy(id);
            message.setReceiveName(String.valueOf(id));
            messageService.insert(message);
        }

    }

    @RequestMapping(value = "/ajax/upload", method = RequestMethod.POST)
    public Result<String> upload(@AuthenticationPrincipal UserDetailsServiceImpl.LoginUserDetails loginUser,
                                 @RequestParam(value = "file") MultipartFile file,
                                 @RequestParam(value = "from", required = false, defaultValue = "card") String from
            , HttpServletResponse resp) {
        resp.setHeader("X-Frame-Options", "SAMEORIGIN");
        Boolean isThumbnail = true;
        Assert.notNull(file, "file is null");
        Result<String> result = new Result<>();
        isThumbnail = null == isThumbnail ? false : isThumbnail;

        //resp.setHeader("Content-Type","text/html;charset=UTF-8");
        com.qipay.admin.home.vo.Resource resource = null;

        try {
            resource = upload(file, new UploadParam((long) loginUser.getId(), isThumbnail));
            if (resource != null) {
                if (resource.getStatus() == 0) {
                    result.setCode(200);
                    result.setData(resource.getUrl());
                } else {
                    result.setCode(resource.getStatus());
                    result.setData("");
                    if (resource.getStatus() == 1) {
                        result.setMsg("文件类型错误");
                    } else if (resource.getStatus() == 2) {
                        result.setMsg("文件大小超过限制");
                    } else {
                        result.setMsg("其它未知错误");
                    }
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
            result.setCode(-1);
            result.setData("服务器内部上传失败");
        }
        return result;
    }

    private com.qipay.admin.home.vo.Resource upload(MultipartFile file, UploadParam param) {

        com.qipay.admin.home.vo.Resource resource = new com.qipay.admin.home.vo.Resource();
        Resource eResource = new Resource();
        eResource.setFileName(file.getOriginalFilename());
        eResource.setFileSize(file.getSize());
        eResource.setCreateTime(new Date());
        eResource.setUserId(param.getUserId());
        BeanUtils.copyProperties(eResource, resource);

        if (!resourceService.checkSize(eResource)) {
            resource.setStatus(ResourceStatusEnum.OUTOFMAXSIZE.getValue());
            return resource;
        }

        InputStream is = null;
        try {
            is = file.getInputStream();
            eResource = resourceService.upload(is, eResource, param.getIsThumbnail());
            resource.setUrl(eResource.getUrl());
            resource.setStatus(ResourceStatusEnum.SUCCESS.getValue());
            logger.info("upload file[{}] to cdn[{}]", eResource.getFileName(), eResource.getUrl());
        } catch (IllegalArgumentException iae) {
            iae.printStackTrace();
            resource.setStatus(ResourceStatusEnum.TYPEERROR.getValue());
        } catch (IOException e) {
            e.printStackTrace();
            resource.setStatus(ResourceStatusEnum.OTHER.getValue());
        } finally {
            IOUtils.closeQuietly(is);
        }

        return resource;
    }
}
